package com.alibaba.citrus.cr.mn.order.center.facade.repository.impl;

import com.alibaba.citrus.cr.common.exception.RepositoryException;
import com.alibaba.citrus.cr.forecast.repository.DictValuesQueryRepository;
import com.alibaba.citrus.cr.forecast.repository.impl.converter.ForecastOrderRepositoryConverter;
import com.alibaba.citrus.cr.mn.order.center.facade.function.convert.ForecastOrderToSDOConvertor;
import com.alibaba.citrus.cr.mn.order.center.facade.repository.ForecastOrderLineQueryRepository;
import com.alibaba.citrus.cr.mn.order.center.facade.repository.ForecastOrderQueryRepository;
import com.alibaba.cz.base.tool.Nullable;
import com.alibaba.cz.base.tool.log.Log;
import com.alibaba.cz.base.tool.page.PageResult;
import com.alibaba.lattice2.epoch.sdk.model.Result;
import com.epoch.app.crforecastsales.domian.forecastorder.dto.BatchQueryForecastByBizNoResponse;
import com.epoch.app.crforecastsales.domian.forecastorder.dto.LoadForecastOrderRequest;
import com.epoch.app.crforecastsales.domian.forecastorder.dto.QueryBySourceNoRequest;
import com.epoch.app.crforecastsales.domian.forecastorder.model.ForecastOrder;
import com.epoch.app.crforecastsales.domian.forecastorder.service.ForecastOrderService;
import com.epoch.app.crforecastsales.model.dto.BatchQueryForecastByBizNoRequest;
import com.epoch.app.crforecastsales.model.dto.SearchForecastOrderRequest;
import com.epoch.app.crforecastsales.ofsforecastorderindex.model.OfsForecastOrderIndex;
import com.epoch.app.crforecastsales.ofsforecastorderindex.service.OfsForecastOrderIndexService;
import com.epoch.app.crforecastsales.sdo.ForecastOrderLineSDO;
import com.epoch.app.crforecastsales.sdo.ForecastOrderSDO;
import com.google.common.collect.Lists;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

@Service("forecastOrderQueryRepositoryBiz")
public class ForecastOrderQueryRepositoryImpl implements ForecastOrderQueryRepository {
    private final Log log = Log.getLogger(ForecastOrderQueryRepositoryImpl.class);

    @Resource
    private ForecastOrderService forecastOrderService;
    @Resource
    private DictValuesQueryRepository dictValuesQueryRepository;
    @Resource
    private ForecastOrderLineQueryRepository forecastOrderLineQueryRepository;
    @Resource
    private OfsForecastOrderIndexService ofsForecastOrderIndexService;

    @Override
    public ForecastOrderSDO queryDetail(String id) {
        if (StringUtils.isBlank(id)) {
            throw new RepositoryException("");
        }
        LoadForecastOrderRequest mainLoadRequest = new LoadForecastOrderRequest();
        mainLoadRequest.setId(id);
        ForecastOrder forecastOrder = forecastOrderService.loadForecastOrder(mainLoadRequest);
        if (Objects.isNull(forecastOrder)) {
            throw new RepositoryException("");
        }
        ForecastOrderSDO forecastOrderSDO = ForecastOrderToSDOConvertor.convert(forecastOrder);
        //赋值子单
        forecastOrderSDO = forecastOrderLineQueryRepository.queryByOrderId(forecastOrderSDO);

        return forecastOrderSDO;
    }

    @Override
    public ForecastOrderSDO queryBySourceOrderNo(QueryBySourceNoRequest sourceNoRequest) {
        Result<ForecastOrder> forecastOrderResult = forecastOrderService.queryBySourceNo(sourceNoRequest);
        if (Objects.nonNull(forecastOrderResult) && Objects.nonNull(forecastOrderResult.getResult())) {
            ForecastOrderSDO convert = ForecastOrderToSDOConvertor.convert(forecastOrderResult.getResult());
            return forecastOrderLineQueryRepository.queryByOrderId(convert);
        }
        return null;
    }

    @Override
    public List<ForecastOrderSDO> queryByOrderBizNo(List<String> bizOrderNos) {
        return queryByOrderBizNo(bizOrderNos, Lists.newArrayList());
    }

    @Override
    public List<ForecastOrderSDO> queryByOrderBizNo(List<String> bizOrderNos, List<String> orderTypeCodeList) {
        log.info("ForecastOrderQueryRepositoryImpl#queryByOrderBizNo bizOrderNos={} orderTypeCodeList={}", bizOrderNos, orderTypeCodeList);
        if (CollectionUtils.isEmpty(bizOrderNos)) {
            return Lists.newArrayList();
        }

        // 查询预报订单主单信息
        BatchQueryForecastByBizNoRequest batchQueryForecastByBizNoRequest = new BatchQueryForecastByBizNoRequest();
        batchQueryForecastByBizNoRequest.setBizNoList(bizOrderNos);
        batchQueryForecastByBizNoRequest.setOrderTypeCodeList(orderTypeCodeList);
        BatchQueryForecastByBizNoResponse byBizNoResponse = forecastOrderService.batchQueryForecastByBizNo(batchQueryForecastByBizNoRequest);
        if (Objects.isNull(byBizNoResponse) || CollectionUtils.isEmpty(byBizNoResponse.getResult())) {
            return Lists.newArrayList();
        }

        // 查询预报订单明细信息
        List<String> mainOrderIds = byBizNoResponse.getResult().stream()
                .map(forecastOrderSDO -> forecastOrderSDO.getId().toString())
                .collect(Collectors.toList());
        PageResult<List<ForecastOrderLineSDO>> listPageResult = forecastOrderLineQueryRepository.batchLoadList(null, mainOrderIds);
        if (CollectionUtils.isEmpty(listPageResult.getContent())) {
            return Lists.newArrayList();
        }
        Map<String, List<ForecastOrderLineSDO>> forecastOrderLineSDOMap = listPageResult.getContent()
                .stream()
                .collect(Collectors.groupingBy(ForecastOrderLineSDO::getMainOrderId));

        // 转换成SDO
        List<ForecastOrderSDO> forecastOrderSDOS = new ArrayList<>();
        for (ForecastOrder forecastOrder : byBizNoResponse.getResult()) {
            ForecastOrderSDO mainForecastOrderSDO = ForecastOrderToSDOConvertor.convert(forecastOrder);
            mainForecastOrderSDO.setForecastOrderLineSDOList(Optional.ofNullable(forecastOrderLineSDOMap.get(forecastOrder.getId().toString())).orElse(new ArrayList<>()));
            forecastOrderSDOS.add(mainForecastOrderSDO);
        }

        return forecastOrderSDOS;
    }

    @Override
    public List<ForecastOrderSDO> queryByOrderBizNoWithBizCode(BatchQueryForecastByBizNoRequest batchQueryForecastByBizNoRequest) {
        List<ForecastOrderSDO> forecastOrderSDOS = new ArrayList<>();
        BatchQueryForecastByBizNoResponse byBizNoResponse = forecastOrderService.batchQueryForecastByBizNo(batchQueryForecastByBizNoRequest);
        if (Objects.nonNull(byBizNoResponse) && CollectionUtils.isNotEmpty(byBizNoResponse.getResult())) {
            for (ForecastOrder forecastOrder : byBizNoResponse.getResult()) {
                ForecastOrderSDO mainForecastOrderSDO = ForecastOrderToSDOConvertor.convert(forecastOrder);
                ForecastOrderSDO forecastOrderSDO = forecastOrderLineQueryRepository.queryByOrderId(mainForecastOrderSDO);
                forecastOrderSDOS.add(forecastOrderSDO);
            }
        }
        return forecastOrderSDOS;
    }

    @Override
    public Result<List<ForecastOrderSDO>> pageQueryByEs(SearchForecastOrderRequest searchForecastOrderRequest) {
        Result<List<OfsForecastOrderIndex>> listResult = ofsForecastOrderIndexService.queryForecastOrderList(searchForecastOrderRequest);
        Map<String, String> enumMap = dictValuesQueryRepository.queryValues("forecastTag");
        List<ForecastOrderSDO> collect = Nullable.stream(listResult.getResult())
                .map(it -> ForecastOrderRepositoryConverter.indexToQueryForecastSDO(it, enumMap))
                .collect(Collectors.toList());
        return Result.listSuccess(collect, listResult.getTotal());
    }

}
